--
-- This file simulates a 512x8 synchronous RAM component.
--
-- The program to be executed is encoded by initializing
-- the "mem_data" signal (see below).
--
--

LIBRARY IEEE;
USE IEEE.std_logic_1164.all;
USE IEEE.std_logic_arith.all;
USE IEEE.std_logic_unsigned.all;

ENTITY microram IS
	PORT (  CLOCK   : IN STD_LOGIC ;
			ADDRESS : IN STD_LOGIC_VECTOR (8 DOWNTO 0);
			DATAOUT : OUT STD_LOGIC_VECTOR (15 DOWNTO 0);
			DATAIN  : IN STD_LOGIC_VECTOR (15 DOWNTO 0);
			WE      : IN STD_LOGIC 
	);
END ENTITY microram;

ARCHITECTURE a OF microram IS
   TYPE t_mem_data IS ARRAY(0 to 511) of std_logic_vector(15 downto 0);

   -- Your program is entered here, as initialization values for
   -- the "mem_data" signal.
   SIGNAL mem_data: t_mem_data :=
	   ( 
		 0 => "0000000011110000",	-- CLR A
		 1 => "0000000000000010",	-- LOAD &VAR_THETA_INIT&,A
		 2 => "0000000011101011",	-- memory pointer &VAR_THETA_INIT&
		 3 => "0000000000000110",	-- STOR A, &VAR_THETA&
		 4 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 5 => "0000000000000010",	-- LOAD &VAR_EPSILON_INIT&,A
		 6 => "0000000011101100",	-- memory pointer &VAR_EPSILON_INIT&
		 7 => "0000000000000110",	-- STOR A, &VAR_EPSILON&
		 8 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 9 => "0000000000000010",	-- LOAD &VAR_POS_INIT&, A, *REFIRE*
		 10 => "0000000011111011",	-- memory pointer &VAR_POS_INIT&
		 11 => "0000000000000110",	-- STOR A, &VAR_YPOS&
		 12 => "0000000011100110",	-- memory pointer &VAR_YPOS&
		 13 => "0000000000000010",	-- LOAD &VAR_LUTMAX&, A
		 14 => "0000000011111100",	-- memory pointer &VAR_LUTMAX&
		 15 => "0000000000000011",	-- LOAD &VAR_THETA&, B
		 16 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 17 => "0000000010010000",	-- SUB A
		 18 => "0000000000000110",	-- STOR A, &VAR_THETACOS&
		 19 => "0000000011111101",	-- memory pointer &VAR_THETACOS&
		 20 => "0000000010001110",	-- SINLUT &VAR_THETACOS&, A
		 21 => "0000000011111101",	-- memory pointer &VAR_THETACOS&
		 22 => "0000000000000110",	-- STOR A, &VAR_XVEL&
		 23 => "0000000011100111",	-- memory pointer &VAR_XVEL&
		 24 => "0000000010001110",	-- SINLUT &VAR_THETA&, A
		 25 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 26 => "0000000000000110",	-- STOR A, &VAR_YVEL&
		 27 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 28 => "0000000000000010",	-- LOAD &VAR_POS_INIT&, A, *CONTINUE_BOUNCE*
		 29 => "0000000011111011",	-- memory pointer &VAR_POS_INIT&
		 30 => "0000000000000110",	-- STOR A, &VAR_XPOS&
		 31 => "0000000011100101",	-- memory pointer &VAR_XPOS&
		 32 => "0000000010010010",	-- CHKTMR &FUNC_START&, *MAINLOOP*
		 33 => "0000000000100100",	-- memory pointer &FUNC_START&
		 34 => "0000000000011100",	-- JMP &MAINLOOP&
		 35 => "0000000000100000",	-- memory pointer &MAINLOOP&
		 36 => "0000000000001100",	-- IN 0, A, *FUNC_START*
		 37 => "0000000000000110",	-- STOR A, &VAR_IN0&
		 38 => "0000000011110001",	-- memory pointer &VAR_IN0&
		 39 => "0000000001100000",	-- BRSET A,0,&CHECKBIT0&
		 40 => "0000000000101011",	-- memory pointer &CHECKBIT0&
		 41 => "0000000000011100",	-- JMP &GOTOBIT1&
		 42 => "0000000001000001",	-- memory pointer &GOTOBIT1&
		 43 => "0000000000000011",	-- LOAD &VAR_OLDIN0&, B, *CHECKBIT0*
		 44 => "0000000011110010",	-- memory pointer &VAR_OLDIN0&
		 45 => "0000000001110000",	-- BRSET B,0,&GOTOBIT1&
		 46 => "0000000001000001",	-- memory pointer &GOTOBIT1&
		 47 => "0000000000000010",	-- LOAD &VAR_EPSILON&, A
		 48 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 49 => "0000000000000011",	-- LOAD &VAR_EPSILON_MIN&, B
		 50 => "0000000011110011",	-- memory pointer &VAR_EPSILON_MIN&
		 51 => "0000000000010110",	-- CPSE
		 52 => "0000000000011100",	-- JMP &DECREMENT_EPSILON&
		 53 => "0000000000111000",	-- memory pointer &DECREMENT_EPSILON&
		 54 => "0000000000011100",	-- JMP &GOTOBIT1&
		 55 => "0000000001000001",	-- memory pointer &GOTOBIT1&
		 56 => "0000000000000011",	-- LOAD &VAR_ONE&, B, *DECREMENT_EPSILON*
		 57 => "0000000011110111",	-- memory pointer &VAR_ONE&
		 58 => "0000000000000010",	-- LOAD &VAR_EPSILON&, A
		 59 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 60 => "0000000010010000",	-- SUB A
		 61 => "0000000000000110",	-- STOR A, &VAR_EPSILON&
		 62 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 63 => "0000000000011100",	-- JMP &GOTOBIT1&
		 64 => "0000000001000001",	-- memory pointer &GOTOBIT1&
		 65 => "0000000000001100",	-- IN 0, A, *GOTOBIT1*
		 66 => "0000000000000110",	-- STOR A, &VAR_IN0&
		 67 => "0000000011110001",	-- memory pointer &VAR_IN0&
		 68 => "0000000001100010",	-- BRSET A,1,&CHECKBIT1&
		 69 => "0000000001001000",	-- memory pointer &CHECKBIT1&
		 70 => "0000000000011100",	-- JMP &GOTOBIT2&
		 71 => "0000000001011110",	-- memory pointer &GOTOBIT2&
		 72 => "0000000000000011",	-- LOAD &VAR_OLDIN0&, B, *CHECKBIT1*
		 73 => "0000000011110010",	-- memory pointer &VAR_OLDIN0&
		 74 => "0000000001110010",	-- BRSET B,1,&GOTOBIT2&
		 75 => "0000000001011110",	-- memory pointer &GOTOBIT2&
		 76 => "0000000000000010",	-- LOAD &VAR_EPSILON&, A
		 77 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 78 => "0000000000000011",	-- LOAD &VAR_EPSILON_MAX&, B
		 79 => "0000000011110100",	-- memory pointer &VAR_EPSILON_MAX&
		 80 => "0000000000010110",	-- CPSE
		 81 => "0000000000011100",	-- JMP &INCREMENT_EPSILON&
		 82 => "0000000001010101",	-- memory pointer &INCREMENT_EPSILON&
		 83 => "0000000000011100",	-- JMP &GOTOBIT2&
		 84 => "0000000001011110",	-- memory pointer &GOTOBIT2&
		 85 => "0000000000000011",	-- LOAD &VAR_ONE&, B, *INCREMENT_EPSILON*
		 86 => "0000000011110111",	-- memory pointer &VAR_ONE&
		 87 => "0000000000000010",	-- LOAD &VAR_EPSILON&, A
		 88 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 89 => "0000000010000000",	-- ADD A
		 90 => "0000000000000110",	-- STOR A, &VAR_EPSILON&
		 91 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 92 => "0000000000011100",	-- JMP &GOTOBIT2&
		 93 => "0000000001011110",	-- memory pointer &GOTOBIT2&
		 94 => "0000000000001100",	-- IN 0, A, *GOTOBIT2*
		 95 => "0000000000000110",	-- STOR A, &VAR_IN0&
		 96 => "0000000011110001",	-- memory pointer &VAR_IN0&
		 97 => "0000000001100100",	-- BRSET A,2,&CHECKBIT2&
		 98 => "0000000001100101",	-- memory pointer &CHECKBIT2&
		 99 => "0000000000011100",	-- JMP &GOTOBIT3&
		 100 => "0000000001111011",	-- memory pointer &GOTOBIT3&
		 101 => "0000000000000011",	-- LOAD &VAR_OLDIN0&, B, *CHECKBIT2*
		 102 => "0000000011110010",	-- memory pointer &VAR_OLDIN0&
		 103 => "0000000001110100",	-- BRSET B,2,&GOTOBIT3&
		 104 => "0000000001111011",	-- memory pointer &GOTOBIT3&
		 105 => "0000000000000010",	-- LOAD &VAR_THETA&, A
		 106 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 107 => "0000000000000011",	-- LOAD &VAR_THETA_MIN&, B
		 108 => "0000000011110101",	-- memory pointer &VAR_THETA_MIN&
		 109 => "0000000000010110",	-- CPSE
		 110 => "0000000000011100",	-- JMP &DECREMENT_THETA&
		 111 => "0000000001110010",	-- memory pointer &DECREMENT_THETA&
		 112 => "0000000000011100",	-- JMP &GOTOBIT3&
		 113 => "0000000001111011",	-- memory pointer &GOTOBIT3&
		 114 => "0000000000000011",	-- LOAD &VAR_ONE&, B, *DECREMENT_THETA*
		 115 => "0000000011110111",	-- memory pointer &VAR_ONE&
		 116 => "0000000000000010",	-- LOAD &VAR_THETA&, A
		 117 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 118 => "0000000010010000",	-- SUB A
		 119 => "0000000000000110",	-- STOR A, &VAR_THETA&
		 120 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 121 => "0000000000011100",	-- JMP &GOTOBIT3&
		 122 => "0000000001111011",	-- memory pointer &GOTOBIT3&
		 123 => "0000000000001100",	-- IN 0, A, *GOTOBIT3*
		 124 => "0000000000000110",	-- STOR A, &VAR_IN0&
		 125 => "0000000011110001",	-- memory pointer &VAR_IN0&
		 126 => "0000000001100110",	-- BRSET A,3,&CHECKBIT3&
		 127 => "0000000010000010",	-- memory pointer &CHECKBIT3&
		 128 => "0000000000011100",	-- JMP &GOTOBIT4&
		 129 => "0000000010011000",	-- memory pointer &GOTOBIT4&
		 130 => "0000000000000011",	-- LOAD &VAR_OLDIN0&, B, *CHECKBIT3*
		 131 => "0000000011110010",	-- memory pointer &VAR_OLDIN0&
		 132 => "0000000001110110",	-- BRSET B,3,&GOTOBIT4&
		 133 => "0000000010011000",	-- memory pointer &GOTOBIT4&
		 134 => "0000000000000010",	-- LOAD &VAR_THETA&, A
		 135 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 136 => "0000000000000011",	-- LOAD &VAR_THETA_MAX&, B
		 137 => "0000000011110110",	-- memory pointer &VAR_THETA_MAX&
		 138 => "0000000000010110",	-- CPSE
		 139 => "0000000000011100",	-- JMP &INCREMENT_THETA&
		 140 => "0000000010001111",	-- memory pointer &INCREMENT_THETA&
		 141 => "0000000000011100",	-- JMP &GOTOBIT4&
		 142 => "0000000010011000",	-- memory pointer &GOTOBIT4&
		 143 => "0000000000000011",	-- LOAD &VAR_ONE&, B, *INCREMENT_THETA*
		 144 => "0000000011110111",	-- memory pointer &VAR_ONE&
		 145 => "0000000000000010",	-- LOAD &VAR_THETA&, A
		 146 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 147 => "0000000010000000",	-- ADD A
		 148 => "0000000000000110",	-- STOR A, &VAR_THETA&
		 149 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 150 => "0000000000011100",	-- JMP &GOTOBIT4&
		 151 => "0000000010011000",	-- memory pointer &GOTOBIT4&
		 152 => "0000000000001100",	-- IN 0, A, *GOTOBIT4*
		 153 => "0000000000000110",	-- STOR A, &VAR_IN0&
		 154 => "0000000011110001",	-- memory pointer &VAR_IN0&
		 155 => "0000000001101000",	-- BRSET A,4,&CHECKBIT4&
		 156 => "0000000010011111",	-- memory pointer &CHECKBIT4&
		 157 => "0000000000011100",	-- JMP &GOTOBIT5&
		 158 => "0000000010100101",	-- memory pointer &GOTOBIT5&
		 159 => "0000000000000011",	-- LOAD &VAR_OLDIN0&, B, *CHECKBIT4*
		 160 => "0000000011110010",	-- memory pointer &VAR_OLDIN0&
		 161 => "0000000001111000",	-- BRSET B,4,&GOTOBIT5&
		 162 => "0000000010100101",	-- memory pointer &GOTOBIT5&
		 163 => "0000000000011100",	-- JMP &REFIRE&
		 164 => "0000000000001001",	-- memory pointer &REFIRE&
		 165 => "0000000000000010",	-- LOAD &VAR_IN0&,A, *GOTOBIT5*
		 166 => "0000000011110001",	-- memory pointer &VAR_IN0&
		 167 => "0000000000000110",	-- STOR A, &VAR_OLDIN0&
		 168 => "0000000011110010",	-- memory pointer &VAR_OLDIN0&
		 169 => "0000000000000010",	-- LOAD &VAR_THETA&,A
		 170 => "0000000011101001",	-- memory pointer &VAR_THETA&
		 171 => "0000000010011100",	-- OUT A, 2
		 172 => "0000000000000010",	-- LOAD &VAR_EPSILON&,A
		 173 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 174 => "0000000010011110",	-- OUT A, 3
		 175 => "0000000000000010",	-- LOAD &VAR_XPOS&,A
		 176 => "0000000011100101",	-- memory pointer &VAR_XPOS&
		 177 => "0000000000000011",	-- LOAD &VAR_YPOS&,B
		 178 => "0000000011100110",	-- memory pointer &VAR_YPOS&
		 179 => "0000000000001000",	-- OUT A, 0
		 180 => "0000000000001011",	-- OUT B, 1
		 181 => "0000000000000010",	-- LOAD &VAR_XVEL&,A
		 182 => "0000000011100111",	-- memory pointer &VAR_XVEL&
		 183 => "0000000000000011",	-- LOAD &VAR_XPOS&,B
		 184 => "0000000011100101",	-- memory pointer &VAR_XPOS&
		 185 => "0000000010000001",	-- ADD B
		 186 => "0000000000000111",	-- STOR B, &VAR_XPOS&
		 187 => "0000000011100101",	-- memory pointer &VAR_XPOS&
		 188 => "0000000000000011",	-- LOAD &VAR_XPOS&,B
		 189 => "0000000011100101",	-- memory pointer &VAR_XPOS&
		 190 => "0000000000000010",	-- LOAD &VAR_X_MAX&,A
		 191 => "0000000011111010",	-- memory pointer &VAR_X_MAX&
		 192 => "0000000010010000",	-- SUB A
		 193 => "0000000010010100",	-- BN &CONTINUE_BOUNCE&
		 194 => "0000000000011100",	-- memory pointer &CONTINUE_BOUNCE&
		 195 => "0000000000011100",	-- JMP &CALCY&
		 196 => "0000000011000101",	-- memory pointer &CALCY&
		 197 => "0000000000000010",	-- LOAD &VAR_YVEL&,A,*CALCY*
		 198 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 199 => "0000000000000011",	-- LOAD &VAR_YPOS&,B
		 200 => "0000000011100110",	-- memory pointer &VAR_YPOS&
		 201 => "0000000010000001",	-- ADD B
		 202 => "0000000010010100",	-- BN &BOUNCE&
		 203 => "0000000011011100",	-- memory pointer &BOUNCE&
		 204 => "0000000000000010",	-- LOAD &VAR_YVEL&,A
		 205 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 206 => "0000000000000011",	-- LOAD &VAR_ACCEL&,B
		 207 => "0000000011101101",	-- memory pointer &VAR_ACCEL&
		 208 => "0000000010010000",	-- SUB A
		 209 => "0000000000000110",	-- STOR A, &VAR_YVEL&
		 210 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 211 => "0000000000000010",	-- LOAD &VAR_YVEL&,A
		 212 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 213 => "0000000000000011",	-- LOAD &VAR_YPOS&,B
		 214 => "0000000011100110",	-- memory pointer &VAR_YPOS&
		 215 => "0000000010000001",	-- ADD B
		 216 => "0000000000000111",	-- STOR B, &VAR_YPOS&
		 217 => "0000000011100110",	-- memory pointer &VAR_YPOS&
		 218 => "0000000000011100",	-- JMP &MAINLOOP&
		 219 => "0000000000100000",	-- memory pointer &MAINLOOP&
		 220 => "0000000000000010",	-- LOAD &VAR_YVEL&,A, *BOUNCE*
		 221 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 222 => "0000000011100000",	-- NEG A
		 223 => "0000000000000110",	-- STOR A, &VAR_YVEL&
		 224 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 225 => "0000000000000011",	-- LOAD &VAR_EPSILON&, B
		 226 => "0000000011101010",	-- memory pointer &VAR_EPSILON&
		 227 => "0000000000000010",	-- LOAD &VAR_ONE&, A
		 228 => "0000000011110111",	-- memory pointer &VAR_ONE&
		 229 => "0000000010000001",	-- ADD B
		 230 => "0000000000000010",	-- LOAD &VAR_YVEL&,A
		 231 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 232 => "0000000000011110",	-- MULT A
		 233 => "0000000000000011",	-- LOAD &VAR_VELMULT&,B
		 234 => "0000000011101111",	-- memory pointer &VAR_VELMULT&
		 235 => "0000000000011110",	-- MULT A
		 236 => "0000000000000110",	-- STOR A, &VAR_YVEL&
		 237 => "0000000011101000",	-- memory pointer &VAR_YVEL&
		 238 => "000000000000011",	-- STOR 0, &VAR_YPOS&
		 239 => "0000000011100110",	-- memory pointer &VAR_YPOS&
		 240 => "0000000000011100",	-- JMP &MAINLOOP&
		 241 => "0000000000100000",	-- memory pointer &MAINLOOP&
		 485 => "0000000000000000",	-- VAR_XPOS = 0
		 486 => "0000000000000000",	-- VAR_YPOS = 0
		 487 => "0000000000000000",	-- VAR_XVEL = 0
		 488 => "0000000000000000",	-- VAR_YVEL = 0
		 489 => "0000000000001100",	-- VAR_THETA = 0b01100
		 490 => "0000000000001100",	-- VAR_EPSILON = 0b1100
		 491 => "0000000000001111",	-- VAR_THETA_INIT = 0b01111
		 492 => "0000000000001100",	-- VAR_EPSILON_INIT = 0b1100
		 493 => "0000000000000101",	-- VAR_ACCEL = 0b0000000000000101
		 494 => "1111111111100000",	-- VAR_NEGONE = 0b1111111111100000
		 495 => "0000000001000000",	-- VAR_VELMULT = 0b1000000
		 496 => "0000000110000000",	-- VAR_FLOOR_OFFEST = 0b110000000
		 497 => "0000000000000000",	-- VAR_IN0 = 0
		 498 => "0000000000000000",	-- VAR_OLDIN0 = 0
		 499 => "0000000000000000",	-- VAR_EPSILON_MIN = 0
		 500 => "0000000000001111",	-- VAR_EPSILON_MAX = 0b1111
		 501 => "0000000000000000",	-- VAR_THETA_MIN = 0
		 502 => "0000000000010000",	-- VAR_THETA_MAX = 0b10000
		 503 => "0000000000000001",	-- VAR_ONE = 1
		 504 => "0000000000000000",	-- VAR_ZERO = 0
		 505 => "0000000111110100",	-- VAR_LUT_POS = 500
		 506 => "0101000000000000",	-- VAR_X_MAX = 0b101000000000000
		 507 => "0000000000000000",	-- VAR_POS_INIT = 0
		 508 => "0000000000010001",	-- VAR_LUTMAX = 17
		 509 => "0000000000000000",	-- VAR_THETACOS = 0
		 510 => "0000000000000000",	-- VAR_EPSILON_LUT = 0
		 511 => "0000000000010011",	-- VAR_EPSILON_LUT_OFFSET = 19

		 others => "0000000000000000"  -- all other memory locations set to 0
			);
BEGIN
   RAM_Process: process(CLOCK)
		VARIABLE memaddr : INTEGER RANGE 0 TO 511;
   BEGIN

		IF rising_edge(CLOCK) THEN
		  memaddr := CONV_INTEGER(ADDRESS);
		  IF we='1' THEN
			 mem_data(memaddr) <= DATAIN;
			 DATAOUT <= DATAIN;
		  ELSE
			 DATAOUT <= mem_data(memaddr);
		  END IF;
		END IF;
	END PROCESS;

END ARCHITECTURE a;	
